package com.wanlian.router.net;

import android.content.Context;
import android.support.annotation.NonNull;
import android.text.TextUtils;

import com.google.gson.Gson;
import com.smart.android.ui.bean.PageInfo;
import com.smart.android.utils.DateTime;
import com.wanlian.router.BuildConfig;
import com.wanlian.router.GlobalInfo;
import com.wanlian.router.bean.Banner;
import com.wanlian.router.bean.Blacklist;
import com.wanlian.router.bean.Conditions;
import com.wanlian.router.bean.Config;
import com.wanlian.router.bean.FeedbackType;
import com.wanlian.router.bean.Integral;
import com.wanlian.router.bean.IntegralFlow;
import com.wanlian.router.bean.IntegralTotal;
import com.wanlian.router.bean.Message;
import com.wanlian.router.bean.MessageCount;
import com.wanlian.router.bean.NetDevice;
import com.wanlian.router.bean.Page;
import com.wanlian.router.bean.RankUser;
import com.wanlian.router.bean.RouterInfo;
import com.wanlian.router.bean.RouterSetting;
import com.wanlian.router.bean.ShareDisk;
import com.wanlian.router.bean.SystemNotice;
import com.wanlian.router.bean.TelecomRechargeCard;
import com.wanlian.router.bean.User;
import com.wanlian.router.bean.WifiSetting;
import com.wanlian.router.bean.YunFile;
import com.wanlian.router.bean.YunMusic;
import com.wanlian.router.bean.YunPictureGroup;
import com.wanlian.router.net.internal.BaseHttpClient;
import com.wanlian.router.net.internal.INetCallBack;
import com.wanlian.router.net.internal.IParser;
import com.wanlian.router.net.internal.Platform;
import com.wanlian.router.net.internal.RequestParams;
import com.wanlian.router.net.internal.ResponseHandleInterface;
import com.wanlian.router.net.res.ArrayBannerResData;
import com.wanlian.router.net.res.ArrayBlacklistResData;
import com.wanlian.router.net.res.ArrayConfigResData;
import com.wanlian.router.net.res.ArrayFeedBackResData;
import com.wanlian.router.net.res.ArrayIntegralFlowResData;
import com.wanlian.router.net.res.ArrayMessageResData;
import com.wanlian.router.net.res.ArrayNetDeviceResData;
import com.wanlian.router.net.res.ArrayRankUserResData;
import com.wanlian.router.net.res.ArraySystemNoticeResData;
import com.wanlian.router.net.res.ArrayTelecomCardResData;
import com.wanlian.router.net.res.ArrayYunFileResData;
import com.wanlian.router.net.res.ArrayYunMusicResData;
import com.wanlian.router.net.res.ArrayYunPictureGroupResData;
import com.wanlian.router.net.res.IntegralResData;
import com.wanlian.router.net.res.IntegralTotalResData;
import com.wanlian.router.net.res.MessageCountResData;
import com.wanlian.router.net.res.MessageResData;
import com.wanlian.router.net.res.RouterInfoResData;
import com.wanlian.router.net.res.RouterSettingResData;
import com.wanlian.router.net.res.ShareDiskResData;
import com.wanlian.router.net.res.UserResData;
import com.wanlian.router.net.res.WifiSettingResData;
import com.wanlian.router.net.res.YunFileResData;
import com.wanlian.router.net.storage.HttpStorage;
import com.wanlian.router.storage.AppData;

import java.io.File;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import okhttp3.Headers;

/**
 * Created by Hyu on 2018/9/3.
 * Email: fvaryu@qq.com
 */
public class NetWorkingClient extends BaseHttpClient {
    private static final NetWorkingClient ourInstance = new NetWorkingClient();

    private NetWorkingClient() {
    }

    public static NetWorkingClient getInstance() {
        return ourInstance;
    }

    @Override
    protected Map<String, String> addHeaders() {
        Map<String, String> map = new HashMap<>();
        map.put("sessionId", AppData.DEFAULT.getSessionId());
        map.put("user-agent", "Android v" + BuildConfig.VERSION_NAME);
        return map;
    }

    @Override
    protected ResponseHandleInterface getResponseHandleInterface(Context context,
                                                                 BaseHttpClient client,
                                                                 Platform mPlatform,
                                                                 boolean printLog,
                                                                 boolean isShow,
                                                                 Object tag,
                                                                 IParser iParser,
                                                                 Gson gson,
                                                                 INetCallBack callBack) {
        return new AsyncHttpResponseHandler(context, client, mPlatform, printLog, isShow, tag, iParser, gson, callBack) {
            @Override
            public void onStop() {

            }
        };
    }

    public void uploadFile(Context context, File file, INetCallBack callBack) {
        upload(context, true, "/upload/file/upload",file, null, callBack );
    }


    private RequestParams page(PageInfo info) {
        info.setTotalSize(Integer.MAX_VALUE);
        return  new RequestParams()
                .put("page",  info.getPageNum())
                .put("num", info.getSize());
    }

    private RequestParams pageObj(PageInfo info) {
        info.setTotalSize(Integer.MAX_VALUE);
        Map<String, Integer> map = new HashMap<>();
        map.put("page", info.getPageNum());
        map.put("num", info.getSize());
        return  new RequestParams()
                .put("page", map);
    }


    public void addFeedback(Context context, String content, String remark, int typeId, List<String> imgPath, INetCallBack callBack) {
        toPost(context, true, "/question/add",
                new RequestParams("content", content).put("typeId", typeId).put("remark", remark)
                        .put("title", "")
                        .put("imgPath", new Gson().toJson(imgPath)), null, callBack
        );
    }

    public void getVcode(Context context, String mobile, INetCallBack callBack) {
        toPost(context, true, "/valitation/msg/code", new RequestParams("mobile", mobile), null, callBack);
    }

    public void register(Context context, String mobile, String code, INetCallBack callBack) {
        toPost(context, true, "/user/register/mobile", new RequestParams("mobile", mobile).put("code", code), null, callBack);
    }

    public void login(Context context, String mobile, String code, INetCallBack<User> callBack) {
        toPost(context, true, "/user/login/mobile", new RequestParams("mobile", mobile).put("code", code), new IParser<User>() {

            @Override
            public User parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, UserResData.class).getObject();
            }
        }, callBack);
    }

    public void modifyUser(Context context, User user, INetCallBack<User> callBack) {
        toPost(context, true, "/user/app/edit", new RequestParams("phone", user.getPhone())
                .put("username", user.getUsername()).put("birthday", DateTime.getDateByb(user.getBirthday()))
                .put("sex", user.isSex()).put("email", user.getEmail()).put("headImg", user.getHeadImg())
                , new IParser<User>(){
                    @Override
                    public User parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        return gson.fromJson(response, UserResData.class).getObject();
                    }
                }, callBack);
    }

    public void userInfo(Context context, INetCallBack<User> callBack) {
        toPost(context, false, "/user/app/query", null, new IParser<User>(){
            @Override
            public User parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, UserResData.class).getObject();
            }
        },callBack);
    }

    public void logout(Context context, INetCallBack callBack) {
        toPost(context, true, "/user/exit", null, null, callBack);
    }

    public void queryBanner(Context context, PageInfo info, INetCallBack<List<Banner>> callBack) {
        toPost(context, false, "/banner/app/list", null, new IParser<List<Banner>>(){
            @Override
            public List<Banner> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, ArrayBannerResData.class).getObject();
            }
        }, callBack);
    }

    public void queryMessage(Context context, final PageInfo info, INetCallBack<List<Message>> callBack) {
        toPost(context, false, "/noticemsg/list/user",
                page(info)
                , new IParser<List<Message>>(){
                    @Override
                    public List<Message> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayMessageResData resData = gson.fromJson(response, ArrayMessageResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }


    public void querySysNotice(Context context, INetCallBack<Message> callBack) {

        toPost(context, false, "/noticemsg/system/new", null, new IParser<Message>(){
            @Override
            public Message parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, MessageResData.class).getObject();
            }
        }, callBack);
    }

    public void querySysMessage(Context context, final PageInfo info, INetCallBack<List<Message>> callBack) {
        toPost(context, false, "/noticemsg/system/user", page(info)
                , new IParser<List<Message>>(){
                    @Override
                    public List<Message> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayMessageResData resData = gson.fromJson(response, ArrayMessageResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

    public void queryMessageCount(Context context, INetCallBack<MessageCount> callBack) {
        toPost(context, false, "/noticemsg/count/user",
                null, new IParser<MessageCount>(){
                    @Override
                    public MessageCount parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        MessageCountResData resData = gson.fromJson(response, MessageCountResData.class);
                        return new MessageCount(resData.getCount());
                    }
                }, callBack);
    }

    public void querySysMessageCount(Context context, INetCallBack<MessageCount> callBack) {
        toPost(context, false, "/noticemsg/system/count", null,  new IParser<MessageCount>(){
                    @Override
                    public MessageCount parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        MessageCountResData resData = gson.fromJson(response, MessageCountResData.class);
                        return new MessageCount(resData.getCount());
                    }
                }, callBack);
    }

    public void updateMessageRead(Context context, long id, INetCallBack callBack) {
        toPost(context, false, "/noticemsg/set/haslook",
                new RequestParams("id", id), null, callBack);
    }

    public void updateMessageAllRead(Context context, INetCallBack callBack) {
        toPost(context, true, "/noticemsg/update/all",
                null, null, callBack);
    }


    public void queryIntegralYesterday(Context context, INetCallBack<Integral> callBack) {
        toPost(context, false, "/score/app/user/score/yes", null, new IParser<Integral>(){
            @Override
            public Integral parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, IntegralResData.class).getObject();
            }
        }, callBack);
    }

    public void queryIntegral(Context context, int rankType, INetCallBack<List<IntegralTotal> > callBack) {
        Map<String, Object> map = new HashMap<String, Object>();
        if (rankType > 0) {
            map.put("rankType", rankType);
        }
        toPost(context, false, "/score/app/user/list",
                pageObj(new PageInfo()).put("conditions",map) , new IParser<List<IntegralTotal> >(){
                    @Override
                    public List<IntegralTotal>  parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        return gson.fromJson(response, IntegralTotalResData.class).getObject();
                    }
                }, callBack);
    }

    public void queryIntegralFlow(Context context, final PageInfo info, INetCallBack<List<IntegralFlow>> callBack) {
        Map<String, String> map = new HashMap<>();
//        map.put("rankType", "");
        toPost(context, false, "/score/app/user/scorewater",
                pageObj(info).put("conditions", map) , new IParser<List<IntegralFlow>>(){
                    @Override
                    public List<IntegralFlow> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayIntegralFlowResData resData = gson.fromJson(response, ArrayIntegralFlowResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

//    public void queryIntegralHistroyFlow(Context context, PageInfo info, INetCallBack callBack) {
//        toPost(context, true, "/score/app/user/scorehistory",
//                pageObj(info).put("conditions", new HashMap<String, Object>()),null, callBack);
//    }

    public void queryTelecomMall(Context context, final PageInfo info, INetCallBack<List<TelecomRechargeCard>> callBack) {
        toPost(context, false, "/product/list/condition",
                pageObj(info).put("conditions", new HashMap<String, Object>()), new IParser<List<TelecomRechargeCard>>(){
                    @Override
                    public List<TelecomRechargeCard> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayTelecomCardResData resData = gson.fromJson(response, ArrayTelecomCardResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

    public void exchageTelecomCard(Context context, TelecomRechargeCard telecomRechargeCard, INetCallBack callBack) {
        Map<String, String> map = new HashMap<>();
        map.put("score", String.valueOf(telecomRechargeCard.getScore()));
               map .put("productId", String.valueOf(telecomRechargeCard.getId()));
               map.put("rankType", String.valueOf(telecomRechargeCard.getRankType()));
        toPost(context, true, "/product/app/exchange",
                new RequestParams("conditions", map), null, callBack);
    }

    public void addShareDisk(Context context, int total, INetCallBack callBack) {
        toPost(context, true, "/device/app/setmemory", new RequestParams("share", total).put("wMemory", 0), null, callBack);
    }

    public void queryShareDiskSize(Context context, INetCallBack<ShareDisk> callBack) {
        toPost(context, false, "/storage/user", null, new IParser<ShareDisk>(){
            @Override
            public ShareDisk parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, ShareDiskResData.class).getObject();
            }
        }, callBack);
    }

    public void queryYunFileDetail(Context context, long id, INetCallBack<YunFile> callBack) {
        toPost(context, true, "/storage/item/query", new RequestParams("id", id), new IParser<YunFile>(){
            @Override
            public YunFile parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, YunFileResData.class).getObject();
            }
        }, callBack);
    }

    public void renameYunFile(Context context, String fileName, long id, INetCallBack callBack) {
        toPost(context, true, "/storage/edit/item", new RequestParams("id", id).put("fileName", fileName), null, callBack);
    }

    public void delectYunFile(Context context, long id, INetCallBack callBack) {
        toPost(context, true, "/storage/item/delete", new RequestParams("id", id), null, callBack);
    }

    public void putFileToYunSys(Context context, String fileName, double fileSize, int fileType, String filePath, INetCallBack callBack ) {
        toPost(context, false, "/storage/add/item",
                new RequestParams("fileName", fileName).put("fileSize", fileSize).put("fileType", fileType).put("filePath", filePath), null, callBack);
    }

    public void queryYunFiles(Context context, final PageInfo info, int fileType, INetCallBack<List<YunFile>> callBack ) {

        Map<String, Object> objectMap = new HashMap<>();
        objectMap.put("fileType", fileType);
        toPost(context, false, "/storage/item/type", pageObj(info).put("conditions",objectMap)
                , new IParser<List<YunFile>>(){
                    @Override
                    public List<YunFile> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayYunFileResData resData = gson.fromJson(response, ArrayYunFileResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

    public void queryYunPictureFiles(Context context, final PageInfo info, int fileType, INetCallBack<List<YunPictureGroup>> callBack ) {

        Map<String, Object> objectMap = new HashMap<>();
        objectMap.put("fileType", fileType);
        toPost(context, false, "/storage/item/type", pageObj(info).put("conditions",objectMap)
                , new IParser<List<YunPictureGroup>>(){
                    @Override
                    public List<YunPictureGroup> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayYunPictureGroupResData resData = gson.fromJson(response, ArrayYunPictureGroupResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

    public void queryFeedbackType(Context context, INetCallBack<List<FeedbackType>> callBack) {
        toPost(context, true, "/question/type/list",
                pageObj(new PageInfo(1, 100)).put("conditions", new HashMap<String, Object>()),
                new IParser<List<FeedbackType>>(){
                    @Override
                    public List<FeedbackType> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        return gson.fromJson(response, ArrayFeedBackResData.class).getObject();
                    }
                }, callBack);
    }

    public void queryTelecomCards(Context context, final PageInfo info, INetCallBack<List<TelecomRechargeCard>> callBack) {
        toPost(context, false, "/card/app/user/list", pageObj(info).put("conditions", new HashMap<String, Object>()), new IParser<List<TelecomRechargeCard>>() {
            @Override
            public List<TelecomRechargeCard> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                ArrayTelecomCardResData resData = gson.fromJson(response, ArrayTelecomCardResData.class);
                info.setTotalSize(resData.getCount());
                return resData.getObject();
            }
        }, callBack);
    }


    static class Type {
        String date = "";

        public Type(String date) {
            this.date = date;
        }
    }
    public void queryIntegralRank(Context context, final PageInfo info, String type, INetCallBack<List<RankUser>> callBack) {
        toPost(context, false, "/score/app/sumscore/order", pageObj(info).put("conditions", new Type(type)), new IParser<List<RankUser>>(){
            @Override
            public List<RankUser> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                ArrayRankUserResData resData = gson.fromJson(response, ArrayRankUserResData.class);
                info.setTotalSize(resData.getCount());
                return resData.getObject();
            }
        }, callBack);
    }

    public void queryAllFlow(Context context, final PageInfo info, INetCallBack callBack) {
        toPost(context, false, "/score/app/user/score/item", pageObj(info).put("conditions", new HashMap<String, Object>()), null, callBack);
    }

    public void switchRouter(Context context, String id , INetCallBack callBack) {
        toPost(context, true, "/device/set/current", new RequestParams("deviceId", id), null, callBack);
    }

    public void deleteRouter(Context context, String id , INetCallBack callBack) {
        toPost(context, true, "/device/untied", new RequestParams("deviceId", id), null, callBack);
    }

    public void bindRouter(Context context, String id, INetCallBack callBack) {
        toPost(context, true, "/device/app/bind", new RequestParams("deviceId", id), null, callBack);
    }

    public void queryUserDevice(Context context, final PageInfo info, INetCallBack<List<NetDevice>> callBack) {
        toPost(context, false, "/device/app/list/user",  pageObj(info).put("conditions", new HashMap<String, Object>()),
                new IParser<List<NetDevice>>(){
                    @Override
                    public List<NetDevice> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayNetDeviceResData resData = gson.fromJson(response, ArrayNetDeviceResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }
                , callBack);
    }

    public void queryBlackList(Context context, final PageInfo info, INetCallBack<List<Blacklist>> callBack) {
        toPost(context, false, "/black/list" , pageObj(info).put("conditions", new HashMap<String, Object>()),
                new IParser<List<Blacklist>>(){
                    @Override
                    public List<Blacklist> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        ArrayBlacklistResData resData = gson.fromJson(response, ArrayBlacklistResData.class);
                        info.setTotalSize(resData.getCount());
                        return resData.getObject();
                    }
                }, callBack);
    }

    public void queryConfig(Context context,boolean isShow, INetCallBack<List<Config>> callBack) {
        toPost(context, isShow, "/config/list",
                pageObj(new PageInfo(1, 100)).put("conditions", new HashMap<String, Object>()),
                new IParser<List<Config>>(){
                    @Override
                    public List<Config> parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                        return gson.fromJson(response, ArrayConfigResData.class).getObject();
                    }
                }, callBack);
    }

    public void queryRouterSetting(Context context, INetCallBack<RouterSetting> callBack) {
        toPost(context, false, "/device/get/setinfo", null,new IParser<RouterSetting>(){
            @Override
            public RouterSetting parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, RouterSettingResData.class).getObject();
            }
        },callBack );
    }

    public void removeBlack(Context context, String id, INetCallBack callBack) {
        toPost(context, true, "/black/edit", new RequestParams("id", id), null, callBack);
    }

    public void add2Black(Context context, String macAddress, String macId, INetCallBack callBack) {
        toPost(context, true, "/black/add", new RequestParams("macAddress", macAddress).put("macId", macId),
                null, callBack);
    }

    public void connectCall(Context context, String networkAccount , String networkPassWord, INetCallBack callBack) {
        toPost(context, true, "/device/config/call", new RequestParams("networkPassWord", networkPassWord).put("networkAccount", networkAccount), null, callBack);
    }

    public void settingWifi(Context context,boolean isNewRouter, boolean isWifiSetting, WifiSetting wifiSetting, INetCallBack callBack) {
        RequestParams params = new RequestParams();
        if (isWifiSetting) {
            if (isNewRouter) {
                params.put(wifiSetting.twoGConfig());
                params.put(wifiSetting.fiveGConfig());
                params.put(wifiSetting.cumtomeConfig());
            }else {
                if (wifiSetting.isHastwoConfig()) {
                    params.put(wifiSetting.twoGConfig());
                }else if (wifiSetting.isHasFiveConfig()) {
                    params.put(wifiSetting.fiveGConfig());
                }else {
                    params.put(wifiSetting.cumtomeConfig());
                }
            }
        }else {
            if ("static".equals(wifiSetting.getSord())) {
                params.put(wifiSetting.staticIpConfig());
            }else {
                params.put(wifiSetting.dynamicIpConfig());
            }
        }

        toPost(context, true, "/device/config/edit", params, null, callBack);
    }

    public void bindINTAccount(Context context, String account, INetCallBack callBack) {
        toPost(context, true, "/user/modify/bindint", new RequestParams("intAccount", account), null, callBack);
    }

    public void unbindINTAccount(Context context, INetCallBack callBack) {
        toPost(context, true, "/user/modify/untiedint", null, null, callBack);
    }

    public void exchangeINT(Context context, double num, INetCallBack callBack) {
        toPost(context, true, "/score/app/score/changeint", new RequestParams("num", num), null, callBack);
    }

    public void queryCurrentRouterInfo(Context context, INetCallBack<RouterInfo> callBack) {
        toPost(context, false, "/device/app/info", null, new IParser<RouterInfo>(){
            @Override
            public RouterInfo parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, RouterInfoResData.class).getObject();
            }
        }, callBack);
    }

    public void querySharedDisk(Context context, INetCallBack<ShareDisk> callBack) {
        toPost(context, false, "/device/app/getmemory", null, new IParser<ShareDisk>(){
            @Override
            public ShareDisk parser(@NonNull Gson gson, int resultCode, Headers headers, String response) {
                return gson.fromJson(response, ShareDiskResData.class).getObject();
            }
        }, callBack);
    }
}
